package com.cong.project.ws;


import com.cong.project.config.MessageUtils;
import com.cong.project.model.entity.Message;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.stereotype.Component;

import javax.websocket.*;
import javax.websocket.server.ServerEndpoint;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;

/**
 * @author lhc
 * @date 2022-08-18 09:26
 */
@ServerEndpoint(value = "/chat", configurator = GetHttpSessionConfigurator.class)
@Component
public class ChatEndpoint {

    /**
     * 用来存储每一个客户端对象的ChatEndpoint对象
     */
    private static Map<Long, ChatEndpoint> onlineUsers = new ConcurrentHashMap<>();

    private static Map<Long,String> NameMap = new HashMap<>();
    /**
     * 声明session对象，通过该对象可以发送消息给指定的用户
     */
    private Session session;
    /**
     * 登录用户的id
     */
    private Long userId;
    /**
     * 登录用户的名字
     */
    private String userName;



    /**
     * 链接建立时被调用
     *
     * @param session
     * @param config
     */
    @OnOpen
    public void onOpen(Session session, EndpointConfig config) {

        this.session = session;

        Long userId = (Long) config.getUserProperties().get("userId");
        this.userId = userId;
        String userName = (String) config.getUserProperties().get("userName");
        this.userName = userName;
        onlineUsers.put(userId, this);
        //将当前在线用户的用户名推送给所有的客户端
        NameMap.put(userId,userName);
        //1获取消息
        String message = MessageUtils.getMessage(true, null,null, getNames());
        //2 调用方法进行系统消息的推送
        broadCastAllUsers(message);
    }

    private void broadCastAllUsers(String message) {
        try {
            //要将该消息推送给所有的客户端
            Set<Long> ids = onlineUsers.keySet();
            for (Long id : ids) {
                ChatEndpoint chatEndpoint = onlineUsers.get(id);
                chatEndpoint.session.getBasicRemote().sendText(message);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }


    private Set<String> getNames(){
        Collection<String> values = NameMap.values();
        Set<String> set = new HashSet<>();
        for (String value : values) {
            set.add(value);
        }
        return set;
    }

    /**
     * 接受到客户端发送的数据时被调用
     *
     * @param message
     * @param session
     */
    @OnMessage
    public void onMessage(String message, Session session) {
        try {
            //将message转换成message对象
            System.out.println(message);
            ObjectMapper mapper = new ObjectMapper();
            Message mess = mapper.readValue(message, Message.class);
            //获取要将数据发送给的用户
            Long toUserId = mess.getToUserId();
            //获取消息数据
            String data = mess.getMessage();

            //获取给指定用户的消息格式
            String resultMessage = MessageUtils.getMessage(false,userName ,userId, data);
            //发送出去
            onlineUsers.get(toUserId).session.getBasicRemote().sendText(resultMessage);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    /**
     * 链接关闭时被调用
     *
     * @param session
     */
    @OnClose
    public void onClose(Session session) {
        //从容器中删除指定用户
        onlineUsers.remove(userId);
        NameMap.remove(userId);
        //获取推送的消息
        String message = MessageUtils.getMessage(true, null, null,getNames());
        System.out.println(message);
        broadCastAllUsers(message);
    }
}
